package nc.bs.common.util;

import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * @author cloudwxjj
 * @date 2024/4/19-下午4:06
 */
public class TimeWatch {

    private final String taskName;

    private final Map<String, Timer> timers = new HashMap<String, Timer>();

    private String lastTask;

    private boolean lastStop;

    private boolean initialized;

    private final String ALL_INVOKE = "ALL INVOKE";

    public TimeWatch() {
        this("~");
    }

    public TimeWatch(String taskName) {
        this.taskName = taskName;
    }

    private void startTask(){
        Timer timer = new Timer();
        timer.start = System.currentTimeMillis();
        timers.put(ALL_INVOKE, timer);
    }

    private void stopTask(){
        Timer timer = timers.get(ALL_INVOKE);
        timer.end = System.currentTimeMillis();
        timers.put(ALL_INVOKE, timer);
    }

    public void start(String name) {
        if(!initialized){
            this.startTask();
            this.initialized = true;
        }
        if(this.lastTask != null && !this.lastStop){
            stop();
        }
        Timer timer = new Timer();
        timer.start = System.currentTimeMillis();
        timers.put(name, timer);
        this.lastTask = name;
        this.lastStop = false;
    }

    public void stop() {
        if (this.lastTask == null) {
            return;
        }
        Timer timer = timers.get(this.lastTask);
        timer.end = System.currentTimeMillis();
        timers.put(this.lastTask, timer);
        this.lastTask = null;
        this.lastStop = true;
    }

    public void record() {
        if (!lastStop) stop();
        this.stopTask();
        this.initialized = false;
        if (!this.timers.isEmpty()) {
            StringBuilder builder = new StringBuilder();
            builder.append("insert into time_watch (task_name,method_name,start_time,end_time,cost_time) ");
            timers.forEach((name, timer) -> {
                builder.append(" select ").append("'").append(taskName).append("'")
                        .append(", '").append(name).append("'")
                        .append(", '").append(getLocalTime(timer.start)).append("'")
                        .append(", '").append(getLocalTime(timer.end)).append("'")
                        .append(", '").append((timer.end - timer.start)).append("'")
                        .append(" from dual union all");
            });
            builder.delete(builder.length() - 9, builder.length());
            DaoUtil.executeUpdate(builder.toString());
        }
    }

    private String getLocalTime(long time) {
        Date date = new Date(time);
        DateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        return dateFormat.format(date);
    }

    static class Timer {
        long start;
        long end;
    }


}
